<!-- 类别设置 -->
<template>
    <div class="box">
        <div class="top">
            <div class="top_one">
                <div class="back" @click="$router.back()">
                    <svg width="40" height="40" viewBox="0 0 40 40" fill="none" xmlns="http://www.w3.org/2000/svg">
                        <path d="M25 5L10 20L25 35" stroke="white" stroke-width="4" stroke-linecap="round" stroke-linejoin="round"/>
                    </svg>
                </div>
                <div class="font_title">类别设置</div>
                <div class="mode-btn" @click="toggleMode">
                    {{ isEditMode ? '删除' : '排序' }}
                </div>
            </div>
            <div class="top_two">
                <div class="expense" 
                     :class="{ 'zcsr_active': currentType === 'expense' }"
                     @click="switchType('expense')">支出</div>
                <div class="income" 
                     :class="{ 'zcsr_active': currentType === 'income' }"
                     @click="switchType('income')">收入</div>
            </div>
        </div>
        <div class="type_cont">
            <div class="item" v-for="category in categories" :key="category._id"
                 :class="{ 'dragging': draggedItem === category._id }"
                 :data-id="category._id">
                <div class="item-content"
                     :class="{ 'edit-mode': isEditMode }"
                     @mousedown="handleMouseDown($event, category)"
                     @touchstart="handleTouchStart($event, category)">
                <div class="left">
                    <svgIcon :iconName="category.icon" font-size="40px"></svgIcon>
                </div>
                <div class="center">
                    {{ category.name }}
                </div>
                <div class="right" v-if="!isEditMode">
                        <div class="delete-btn" @click="handleDelete(category)">
                    <svgIcon iconName="icon-shanchu" 
                            font-size="30px" 
                            color="#000" 
                                    class="delete-icon"></svgIcon>
                        </div>
                </div>
                <div class="right" v-else>
                    <div class="drag-handle">
                        <svgIcon iconName="icon-paixu" 
                                font-size="30px" 
                                color="#000"></svgIcon>
                    </div>
                </div>
            </div>    
        </div>
        </div>
        <div class="bottom" @click="goToAddCategory">
            +添加类别
        </div>

        <MessageBox ref="messageBox" />
    </div>
</template>

<script setup>
import { ref, onMounted } from 'vue';
import { useRouter } from 'vue-router';
import MessageBox from '../components/MessageBox.vue';
import request from '../utils/request';

const router = useRouter();
const categories = ref([]);
const currentType = ref('expense');
const isEditMode = ref(true);
const draggedItem = ref(null);
const dragStartY = ref(0);
const dragStartTop = ref(0);
const currentDragItem = ref(null);
const originalOrder = ref([]);
const newCategory = ref({
    name: '',
    icon: '',
    type: 'expense',
    order: 0
});

const messageBox = ref(null);

// 获取类别数据
const fetchCategories = async (type) => {
    try {
        const response = await request.get(`/api/category/categories?type=${type}`);
        categories.value = response.data;
    } catch (error) {
        console.error('获取类别数据失败:', error);
    }
};

// 切换类别类型
const switchType = (type) => {
    currentType.value = type;
    newCategory.value.type = type;
    fetchCategories(type);
};

// 处理鼠标按下事件
const handleMouseDown = (e, category) => {
    if (!isEditMode.value) {
        return;
    }
    e.preventDefault();
    e.stopPropagation();
    startDrag(e, category);
};

// 处理触摸开始事件
const handleTouchStart = (e, category) => {
    if (!isEditMode.value) {
        return;
    }
    e.preventDefault();
    e.stopPropagation();
    startDrag(e, category);
};

// 开始拖动
const startDrag = (e, category) => {
    // 如果是非编辑模式（显示"排序"），不启动拖动
    if (!isEditMode.value) {
        return;
    }
    
    console.log('开始拖动:', category.name);
    const item = e.target.closest('.item');
    if (!item) return;

    draggedItem.value = category._id;
    currentDragItem.value = item;
    
    // 记录起始位置
    if (e.type === 'mousedown') {
        dragStartY.value = e.clientY;
    } else if (e.type === 'touchstart') {
        dragStartY.value = e.touches[0].clientY;
    }
    dragStartTop.value = item.offsetTop;

    // 保存原始顺序
    originalOrder.value = [...categories.value];

    // 添加拖动事件监听
    if (e.type === 'mousedown') {
        document.addEventListener('mousemove', handleDrag);
        document.addEventListener('mouseup', stopDrag);
    } else {
        document.addEventListener('touchmove', handleDrag, { passive: false });
        document.addEventListener('touchend', stopDrag);
    }
};

// 检查顺序是否发生变化
const hasOrderChanged = () => {
    if (!originalOrder.value.length) return false;
    
    return categories.value.some((category, index) => {
        return category._id !== originalOrder.value[index]._id;
    });
};

// 处理拖动
const handleDrag = (e) => {
    if (!draggedItem.value || !currentDragItem.value) return;
    e.preventDefault();

    // 获取当前位置
    const currentY = e.type === 'mousemove' ? e.clientY : e.touches[0].clientY;
    const deltaY = currentY - dragStartY.value;
    
    // 使用 transform3d 强制启用硬件加速
    currentDragItem.value.style.transform = `translate3d(0, ${deltaY}px, 0)`;
    
    // 获取所有项目
    const items = Array.from(document.querySelectorAll('.item'));
    const draggedRect = currentDragItem.value.getBoundingClientRect();
    const draggedCenter = draggedRect.top + draggedRect.height / 2;
    
    // 找到目标位置
    let targetItem = null;
    let minDistance = Infinity;
    const threshold = draggedRect.height * 0.3;
    
    for (const item of items) {
        if (item === currentDragItem.value) continue;
        
        const rect = item.getBoundingClientRect();
        const center = rect.top + rect.height / 2;
        const distance = Math.abs(draggedCenter - center);
        
        if (distance < minDistance && distance < threshold) {
            minDistance = distance;
            targetItem = item;
        }
    }
    
    // 如果找到目标项，交换位置
    if (targetItem) {
        const fromIndex = categories.value.findIndex(c => c._id === draggedItem.value);
        const toIndex = categories.value.findIndex(c => c._id === targetItem.getAttribute('data-id'));
        
        if (fromIndex !== toIndex) {
            // 更新数组
            const [movedItem] = categories.value.splice(fromIndex, 1);
            categories.value.splice(toIndex, 0, movedItem);
            
            // 更新DOM
            requestAnimationFrame(() => {
                const container = currentDragItem.value.parentNode;
                
                // 为所有项添加过渡效果
                items.forEach(item => {
                    if (item !== currentDragItem.value) {
                        item.setAttribute('style', 'transition: transform 0.5s cubic-bezier(0.4, 0, 0.2, 1)');
                    }
                });
                
                // 直接更新DOM位置
                if (fromIndex < toIndex) {
                    container.insertBefore(currentDragItem.value, targetItem.nextSibling);
                } else {
                    container.insertBefore(currentDragItem.value, targetItem);
                }
                
                // 更新起始位置
                dragStartTop.value = currentDragItem.value.offsetTop;
                dragStartY.value = currentY;
                
                // 重置样式
                setTimeout(() => {
                    items.forEach(item => {
                        if (item !== currentDragItem.value) {
                            item.removeAttribute('style');
                        }
                    });
                }, 500);
            });
        }
    }
};

// 保存类别顺序
const saveOrder = async () => {
    // 检查顺序是否真的改变了
    if (!hasOrderChanged()) {
        console.log('顺序未改变，跳过保存');
        return;
    }

    try {
        // 构建更新数据，只包含必要的字段
        const updateData = categories.value.map((category, index) => ({
            _id: category._id,
            order: index + 1
        }));

        console.log('发送的排序数据:', JSON.stringify(updateData, null, 2));

        // 发送更新请求
        const response = await request.post('/api/category/updateOrder', {
            type: currentType.value,
            categories: updateData
        }, {
            headers: {
                'Content-Type': 'application/json'
            }
        });

        // 检查响应
        if (response.data.success) {
            console.log('服务器响应:', response.data);
            // 保存成功后，重新获取数据
            await fetchCategories(currentType.value);
            console.log('顺序保存并更新成功');
        } else {
            // 只有在服务器明确返回失败时才抛出错误
            if (response.data.message && response.data.message !== '排序更新成功') {
                throw new Error(response.data.message);
            }
            // 如果是成功消息，直接处理
            console.log('服务器响应:', response.data);
            await fetchCategories(currentType.value);
            console.log('顺序保存并更新成功');
        }
    } catch (error) {
        console.error('保存顺序失败:', error);
        // 如果保存失败，重新获取数据
        await fetchCategories(currentType.value);
    }
};

// 停止拖动
const stopDrag = async () => {
    if (!draggedItem.value || !currentDragItem.value) return;
    
    // 移除事件监听
    document.removeEventListener('mousemove', handleDrag);
    document.removeEventListener('mouseup', stopDrag);
    document.removeEventListener('touchmove', handleDrag);
    document.removeEventListener('touchend', stopDrag);
    
    // 重置样式
    currentDragItem.value.style.transform = '';
    
    // 只有在顺序真正改变时才保存
    if (hasOrderChanged()) {
        try {
            await saveOrder();
        } catch (error) {
            console.error('保存顺序时出错:', error);
        }
    }
    
    // 重置状态
    draggedItem.value = null;
    currentDragItem.value = null;
    dragStartY.value = 0;
    dragStartTop.value = 0;
};

// 切换编辑模式
const toggleMode = () => {
    console.log('切换模式前:', isEditMode.value ? '编辑模式' : '普通模式');
    isEditMode.value = !isEditMode.value;
    console.log('切换模式后:', isEditMode.value ? '编辑模式' : '普通模式');
    
    // 重置所有状态
    draggedItem.value = null;
    currentDragItem.value = null;
    dragStartY.value = 0;
    dragStartTop.value = 0;
};


// 处理删除按钮点击
const handleDelete = (category) => {
    console.log('handleDelete 被调用', category.name);
    if (!messageBox.value) {
        console.error('messageBox 未挂载');
        return;
    }
    messageBox.value.show(`是否删除"${category.name}"类别？`, () => {
        console.log('用户确认删除');
        deleteCategory(category);
    });
};

// 删除类别
const deleteCategory = async (category) => {
    try {
        console.log('开始删除类别:', category._id);
        const response = await request.delete(`/api/category/categories/${category._id}`, null, {
            headers: {
                'Content-Type': 'application/json'
            }
        });
        console.log('删除响应:', response);
        
        // 检查响应状态
        if (response.status === 200 || response.status === 204) {
            console.log('删除成功，重新获取数据');
            await fetchCategories(currentType.value);
            return;
        }
        
        // 如果响应包含错误信息
        if (response.data && !response.data.success) {
            throw new Error(response.data.message || '删除失败');
        }
        
        // 默认成功情况
        console.log('删除成功，重新获取数据');
        await fetchCategories(currentType.value);
    } catch (error) {
        console.error('删除类别失败:', error);
        console.error('错误详情:', {
            message: error.message,
            response: error.response?.data,
            status: error.response?.status
        });
        messageBox.value.show(error.message || '删除失败，请重试', null);
    }
};

// 跳转到添加类别页面
const goToAddCategory = () => {
    router.push({
        path: '/add-category',
        query: { type: currentType.value }
    });
};

// 组件挂载时获取数据
onMounted(() => {
    fetchCategories(currentType.value);
});
</script>

<style lang='less' scoped>
.box {
    width: 100%;
    height: 100vh;
    position: relative;
    overflow: hidden;
    
    .top {
        width: 100%;
        height: 230px;
        background-color: #fb8fae;
        color: #fff;
        position: fixed;
        top: 0;
        left: 0;
        z-index: 100;
        .top_one {
            width: 100%;
            height: 100px;
            display: flex;
            align-items: center;
            justify-content: space-around;
            .back {
                width: 120px;
                height: 100%;
                margin-left: 20px;
                line-height: 50px;
                text-align: center;
                display: flex;
                align-items: center;
                svg {
                    width: 40px;
                    height: 40px;
                }
            }
            .font_title {
                font-size: 32px;
                margin: 0 auto;
            }
            .mode-btn {
                margin-right: 20px;
                width: 120px;
                font-size: 28px;
                text-align: center;
                height: 100%;
                line-height: 100px;
                cursor: pointer;
                transition: all 0.3s ease;
                
                &:active {
                    opacity: 0.7;
                }
            }
        }
        .top_two {
            width: 100%;
            height: 130px;
            display: flex;
            justify-content: center;
            align-items: center;
            font-size: 32px;
            .expense {
                width: 210px;
                height: 60px;
                border-radius: 10px 0 0 10px;
                border: 1px solid #fff;
                text-align: center;
                line-height: 60px;
            }
            .income {
                width: 210px;
                height: 60px;
                border-radius: 0 10px 10px 0;
                border: 1px solid #fff;
                text-align: center;
                line-height: 60px;
            }
            .zcsr_active {
                background-color: #fff;
                color: #fb8fae;
            }

        }
    }
    .type_cont {
        width: 100%;
        height: calc(100vh - 330px);
        margin-top: 230px;
        margin-bottom: 100px;
        background-color: #fff;
        overflow-y: auto;
        -webkit-overflow-scrolling: touch;
        user-select: none; // 防止拖动时选中文字
        
        .item {
                width: 100%;
                height: 90px;
                background-color: #fff;
            position: relative;
            
            .item-content {
                width: 100%;
                height: 100%;
                display: flex;
                align-items: center;
                padding: 0 40px;
                border-bottom: 1PX solid gray;
                position: relative;
                cursor: pointer;
                will-change: transform;
                transform: translate3d(0, 0, 0);
                backface-visibility: hidden;
                -webkit-backface-visibility: hidden;
                perspective: 1000;
                -webkit-perspective: 1000;

                &.edit-mode {
                    cursor: grab;
                }
            }

            &.dragging {
                opacity: 0.6;
                z-index: 100;
                background-color: #f8f8f8;
                box-shadow: 0 4px 12px rgba(0, 0, 0, 0.1);
                cursor: grabbing;
                transform: translate3d(0, 0, 0);
                border-radius: 8px;
                border: 1px solid #eee;
                transition: none !important;
            }

            .left {
                    width: 40px;
                    height: 40px;
                pointer-events: none;
                }

            .center {
                    width: 550px;
                    margin-left: 20px;
                    font-size: 32px;
                    color: #000;
                pointer-events: none;
                }

            .right {
                width: 60px;
                height: 60px;
                display: flex;
                align-items: center;
                justify-content: center;
                position: relative;
                z-index: 100;
            }

            .delete-btn {
                    width: 60px;
                    height: 60px;
                    display: flex;
                    align-items: center;
                    justify-content: center;
                cursor: pointer;
                position: relative;
                z-index: 101;
                touch-action: none;
                
                &:active {
                    opacity: 0.7;
                }
                
                .delete-icon {
                    pointer-events: none;
                }
                }
        }
    }
    .bottom {
        width: 100%;
        height: 100px;
        background-color: #f0f0f0;
        position: fixed;
        bottom: 0;
        left: 0;
        color: #000;
        text-align: center;
        line-height: 100px;
        font-size: 32px;
        z-index: 100;
        cursor: pointer;
        
        &:active {
            opacity: 0.8;
        }
    }
}

.modal {
    position: fixed;
    top: 0;
    left: 0;
    width: 100%;
    height: 100%;
    background: rgba(0, 0, 0, 0.5);
    display: flex;
    justify-content: center;
    align-items: center;
    z-index: 1000;

    .modal-content {
        background: white;
        padding: 20px;
        border-radius: 10px;
        width: 80%;
        max-width: 500px;

        h3 {
            margin-bottom: 20px;
            text-align: center;
        }

        input {
            width: 100%;
            padding: 10px;
            margin-bottom: 15px;
            border: 1px solid #ddd;
            border-radius: 5px;
        }

        .modal-buttons {
            display: flex;
            justify-content: space-around;
            margin-top: 20px;

            button {
                padding: 10px 20px;
                border: none;
                border-radius: 5px;
                background: #fb8fae;
                color: white;
                cursor: pointer;

                &:last-child {
                    background: #999;
                }
            }
        }
    }
}

.type_cont {
    .item {
        &:not(.dragging) {
            transition: transform 0.5s cubic-bezier(0.4, 0, 0.2, 1);
        }
    }
}

.delete-btn {
    width: 60px;
    height: 60px;
    display: flex;
    align-items: center;
    justify-content: center;
    cursor: pointer;
    pointer-events: auto;
    z-index: 10;
    
    &:active {
        opacity: 0.7;
    }
    
    .delete-icon {
        pointer-events: none;
    }
}
</style>
